import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * @author pinker on 2018/3/15
 */
public class AysPrint {
  volatile int index = 0;
  volatile boolean flag = true;

  public static void main(String[] args) throws InterruptedException {
    AysPrint demo = new AysPrint();
//        demo.test1();
    demo.test2();
//        demo.test3();
  }

  /**
   * 典型的生产者消费者模型!
   *
   * @throws InterruptedException
   */
  private void test3() throws InterruptedException {
    String str="le";
    str.length();
    int a[]={1,2,3};
    int count =a.length;
    Object obj = new Object();
    final Runnable r = () -> {
      while (index <= 20) {
        synchronized (obj) {
          try {
            System.out.println(Thread.currentThread().getName() + "|" + index++);
            obj.notify();
            Thread.sleep(1000);
            obj.wait();
          } catch (InterruptedException e) {
            e.printStackTrace();
          }
        }
      }
    };
    Thread t1 = new Thread(r);
    Thread t2 = new Thread(r);
    t1.start();
    t2.start();
    t1.join();
    t2.join();
  }

  /**
   * 结果证明lock,unlock并不能保证交替执行!
   *
   * @throws InterruptedException
   */
  private void test2() throws InterruptedException {
    final int[] i = {0};
    final Lock lock = new ReentrantLock();
    final Runnable r = () -> {
      while (i[0] < 20) {
        try {
          lock.lock();
          Thread.sleep(1000);
          System.out.println(Thread.currentThread().getName() + "|" + i[0]++);
        } catch (InterruptedException e) {
          e.printStackTrace();
        } finally {
          lock.unlock();
        }
      }
    };
    Thread t1 = new Thread(r);
    Thread t2 = new Thread(r);
    t1.start();
    t2.start();
    t1.join();
    t2.join();
  }

  public void test1() {
    Thread t1 = new Thread(new PrintTask());
    Thread t2 = new Thread(new PrintTask1());
    t1.start();
    t2.start();
  }

  class PrintTask1 implements Runnable {

    @Override
    public void run() {
      while (true) {
        if (!flag) {
          System.out.println(Thread.currentThread().getName() + "\t" + index++);
          try {
            Thread.sleep(1000);
            flag = !flag;
          } catch (InterruptedException e) {
            e.printStackTrace();
          }
        }
      }
    }
  }

  class PrintTask implements Runnable {

    @Override
    public void run() {
      while (true) {
        if (flag) {
          System.out.println(Thread.currentThread().getName() + "\t" + index++);
          try {
            Thread.sleep(1000);
            flag = !flag;
          } catch (InterruptedException e) {
            e.printStackTrace();
          }
        }
      }
    }
  }
}

